#include <8052.h>

#include "misc.h"
#include "lcd1602.h"

//lcden = P3_4 //液晶使能
//lcdrs = P3_5 //数据/命令 选择  (H/L)

void write_cmd(unsigned char cmd);
void write_data(unsigned char data);

void lcd1602_show()
{
    __code char strData1[] = "Hello world!";
    __code char strData2[] = "http://www.81vp.com";

    //通过传递数组名参数到子函数中，以获得数组长度是不可行的
    //获得数组长度，只能在数组定义所在的代码区中
    unsigned char size1 = sizeof(strData1) / sizeof(strData1[0]);
    unsigned char size2 = sizeof(strData2) / sizeof(strData2[0]);
    //重置段选位选
    P2_6 = P2_7 = 0;

    P3_4 = 0;
    write_cmd(0b00111000); //显示模式设置
    write_cmd(0b00001111); //显示开，光标闪烁
    write_cmd(0b00000110); //整屏左移
    write_cmd(0x01);       //清屏

    //+16是让它写在后面，方便整屏左移
    int addr = 0x80 + 16;
    write_cmd(addr); //指针，第一行
    char i = 0;
    for (i = 0; i < size1 - 1; i++)
    {
        write_data(strData1[i]);
    }
    //+0x40是指放在第二排
    //+16是让它写在后面，方便整屏左移
    addr = 0x80 + 0x40 + 16;
    write_cmd(addr); //指针，第二行
    for (i = 0; i < size2 - 1; i++)
    {
        write_data(strData2[i]);
    }
    //整屏左移
    for (i = 0; i < 16; i++)
    {
        write_cmd(0b00011000);
        delay(500);
    }
    while (1)
        ;
}

void write_cmd(unsigned char cmd)
{
    P3_5 = 0; //命令方式
    P0 = cmd;
    P3_4 = 1; //启动
    delay(10);
    P3_4 = 0;
}

void write_data(unsigned char data)
{
    P3_5 = 1; //数据方式
    P0 = data;
    P3_4 = 1; //启动
    delay(10);
    P3_4 = 0;
}

//把数字显示在屏幕上
void lcd1602_show_number(int data)
{
    P3_4 = 0;
    write_cmd(0b00111000); //显示模式设置
    write_cmd(0b00001100); //显示开，光标闪烁
    write_cmd(0b00000110); //整屏左移
    write_cmd(0x01);       //清屏

    //+16是让它写在后面，方便整屏左移
    // int addr = 0x80 + 0;
    // write_cmd(addr); //指针，第一行

    //使用堆栈把数据倒序
    char stack[10];
    char count = 0;
    do
    {
        stack[count++] = data % 10;
        data /= 10;
    } while (data > 0);
    while (count--)
    {
        //转换为assic码
        char d = stack[count] + 48;
        write_data(d);
    }
}


void lcd1602_show_str(unsigned char *str, unsigned char len){
    P3_4 = 0;
    write_cmd(0b00111000); //显示模式设置
    write_cmd(0b00001100); //显示开，光标闪烁
    write_cmd(0b00000110); //整屏左移
    write_cmd(0x01);       //清屏

    while (len--){ //连续写入 len 个字符数据
        write_data(*str++); //先取 str 指向的数据，然后 str 自加1
    }
}